package com.boby.homecamera.webserver.websocket

import com.boby.homecamera.constant.Constant
import com.boby.homecamera.data.WebSocketData
import com.boby.homecamera.db.VideoEventTable
import com.boby.homecamera.util.JsonUtils
import com.boby.lib_common.BaseApplication
import com.boby.lib_common.util.BLog
import com.boby.lib_common.util.JsonUtil
import org.java_websocket.WebSocket
import org.java_websocket.client.WebSocketClient
import org.java_websocket.handshake.ServerHandshake
import org.json.JSONObject
import java.net.URI

class MsgEventWebSocketClient(val deviceId:String,var ip:String,var port:Int,var token: String) {
    private val TAG = "MsgEventWebSocketClient"
    private var client: WebSocketClient? = null
    private var isStart = false
    private var videoEventListener:((videoEvent: VideoEventTable.VideoEvent) -> Unit)? = null
    fun setVideoEventListener(listener:((videoEvent: VideoEventTable.VideoEvent) -> Unit)?) {
        videoEventListener = listener
    }
    fun start(){
        isStart = true
        connect()
    }
    fun close(){
        BaseApplication.getWorkHandler()?.removeCallbacks(reconnectRunnable)
        client?.close()
        client = null
        isStart = false
    }

    private fun connect(){
        if(!isStart){
            return
        }
//        val uri = URI("ws://${ip}:${Constant.WEBSOCKET_PORT}/ws?token=${token}")
        val uri = URI("ws://${ip}:${port}/ws?token=${token}")
        client = object : WebSocketClient(uri) {
            override fun onOpen(handshakedata: ServerHandshake?) {
                BLog.d(TAG,"连接成功")
            }

            override fun onMessage(msg: String?) {
//                BLog.d(TAG,"收到消息: $msg")
                if (msg.isNullOrEmpty()) {
                    return
                }
                try {
                    val jsonObject = JSONObject(msg)
                    if(jsonObject.has("code")){
                        val code  = jsonObject.getInt("code")
                        handlerMsg(code,jsonObject)
                    }

                }catch (e: java.lang.Exception){
                    e.printStackTrace()
                }
            }

            override fun onClose(code: Int, reason: String?, remote: Boolean) {
                if(code == Constant.WebSocketCode.CONNECT_ERROR){
                    return
                }
                reconnectDelay()
            }
            override fun onError(ex: Exception?) {
                ex?.printStackTrace()
                reconnectDelay()
            }
        }

        client?.connect()
    }

    fun send(message: String){
        client?.send(message)
    }
    fun sendAudio(byteArray: ByteArray){
//        BLog.d(TAG, "audioCall: sendMessage ${byteArray.size}")
        client?.send(byteArray)

    }

     fun reconnectDelay(){
        if(!isStart){
            return
        }
        BaseApplication.getWorkHandler()?.removeCallbacks(reconnectRunnable)
        BaseApplication.getWorkHandler()?.postDelayed(reconnectRunnable,1000)
    }
    private val reconnectRunnable = Runnable {
        connect()

    }
    private fun handlerMsg(code:Int,jsonObject: JSONObject){
        when(code){
            Constant.WebSocketCode.EVENT_MSG ->  eventMsg(jsonObject)
        }
    }
    private fun eventMsg(jsonObject: JSONObject){
        val data = jsonObject.get("data")
//        BLog.d(TAG, "eventMsg: $data ,is String:${data is String}")
        if(data != null && data is String){
            val videoEvent = JsonUtil.fromJson<VideoEventTable.VideoEvent>(data)
            videoEventListener?.invoke(videoEvent)
        }

        //WebSocketData
    }

}